package com.ranlen.ems_vue.controller;

import com.ranlen.ems_vue.cache.UserCache;
import com.ranlen.ems_vue.entity.User;
import com.ranlen.ems_vue.service.UserService;
import com.ranlen.ems_vue.service.serviceImpl.UserServiceImpl;
import com.ranlen.ems_vue.utils.SerializeUtil;
import com.ranlen.ems_vue.utils.VerifyCodeUtils;
import lombok.extern.slf4j.Slf4j;
import org.apache.logging.log4j.util.Strings;
import org.jasypt.encryption.StringEncryptor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.web.servlet.server.Session;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.serializer.StringRedisSerializer;
import org.springframework.util.Base64Utils;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import java.util.concurrent.TimeUnit;

@RestController
@CrossOrigin
@RequestMapping("user")
@Slf4j
public class UserController {
    @Autowired
    private UserService userService;

    @Autowired
    UserCache userCache;

    @Autowired
    RedisTemplate redisTemplate;
    @Autowired
    private StringRedisTemplate stringRedisTemplate;

    //生成验证码图片
    @RequestMapping("getImage")
    public String getImageCode(HttpServletRequest request) throws IOException {
        //生成验证码
        String code = VerifyCodeUtils.generateVerifyCode(4);
        //将验证码放入servletContext作用域
        //request.getServletContext().setAttribute("code",code);

        //将验证码放入redis
        stringRedisTemplate.opsForValue().set("code",code);
        //设置有效时间
        stringRedisTemplate.expire("code",60, TimeUnit.SECONDS);

        //将图片转为base64
        ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
        VerifyCodeUtils.outputImage(150,40,byteArrayOutputStream,code);
        String s = Base64Utils.encodeToString(byteArrayOutputStream.toByteArray());
        return "data:image/png;base64,"+s;
    }

    //用户注册
    @PostMapping("register")
    public Map<String,Object> register(@RequestBody User user,String code, HttpServletRequest request){
        log.info("用户信息：[{}]",user.toString());
        log.info("用户输入验证码：[{}]",code);
        Map<String,Object> map = new HashMap<>();
        try {
            //String key = (String) request.getServletContext().getAttribute("code");
            String key = stringRedisTemplate.opsForValue().get("code");
            if (key.equalsIgnoreCase(code)){
                userService.register(user);
                map.put("state",true);
                map.put("msg","提示：注册成功");
            }else {
                throw new RuntimeException("验证码错误");
            }
        } catch (Exception e) {
            e.printStackTrace();
            map.put("state",false);
            map.put("msg","提示："+e.getMessage());
        }
        return map;
    }

    //处理登录
    @PostMapping("login")
    public Map<String,Object> login(@RequestBody User user,HttpServletRequest request){
        log.info("用户信息：[{}]",user.toString());
        Map<String,Object> map = new HashMap<>();
        try {
            User user1 = userService.login(user);

            //用户信息存入redis
            String token = UUID.randomUUID().toString();
            stringRedisTemplate.opsForValue().set(token,token+user1.getId());
            stringRedisTemplate.expire(token,2, TimeUnit.HOURS);
            //设置key的序列化规则
            redisTemplate.setKeySerializer(new StringRedisSerializer());
            redisTemplate.opsForValue().set(token+user1.getId(),user1);
            redisTemplate.expire(user1.getId(),2,TimeUnit.HOURS);
            request.getSession().setAttribute("token",token);
            map.put("token",token);
            map.put("state",true);
            map.put("user",user1);
            map.put("msg","登录成功");
        } catch (Exception e) {
            e.printStackTrace();
            map.put("state",false);
            map.put("msg",e.getMessage());
        }
        return map;
    }
    @GetMapping("getUser")
    public Map<String,Object> getUser(HttpServletRequest request){
        Map<String,Object> map = new HashMap<>();
        String token = (String) request.getSession().getAttribute("token");
        log.info("用户的token：[{}]",token);
        if (Strings.isBlank(token)){
            map.put("state",false);
            map.put("msg","未登录...");
        }else {
            String key = stringRedisTemplate.opsForValue().get(token);
            User user = (User)redisTemplate.opsForValue().get(key);
            map.put("state",true);
            log.info("用户的token信息：[{}]",user.toString());
            map.put("user",user);
        }
        return map;
    }
    @GetMapping("logout")
    public Map<String,Object> logout(HttpServletRequest request){
        Map<String,Object> map = new HashMap<>();
        HttpSession session = request.getSession();
        String token = (String) session.getAttribute("token");
        String key = stringRedisTemplate.opsForValue().get(token);
        redisTemplate.delete(key);
        stringRedisTemplate.delete(token);
        session.removeAttribute("token");
        log.info("用户退出");
        map.put("state",true);
        map.put("msg","未登录...");
        return map;
    }
}
